# -*- coding: utf-8 -*-
import sys
sys.path.append("../../quidditas")

import pygame
import cyrusbus

import quidditas
from pygame.time import Clock
from pygame.image import load

import type_definitions, processors, components

class Asteroids(object):
    """ Class definition for the asteroids game. """

    def __init__(self):
        """ Create a new instance of the asteroids game. """
        pygame.init()
        pygame.display.set_caption("Asteroids example using Quidditas")

        screen = pygame.display.set_mode((640, 480))
        self.clock = Clock()

        self.to_update = []
        self.to_render= []

        self.event_bus = cyrusbus.Bus()
        self.event_bus.subscribe("event.exit", self.on_exit)

        images = {}
        images["asteroid"] = load("res/asteroid.png")
        images["spaceship"] = load("res/player.png")
        self.q = self.init_quidditas(screen, images)

    def on_exit(self, event):
        """ Handle an exit event that comes via the event bus. """
        self.running = 0

    def start(self):
        """ Start the game loop. """

        self.running = 1
        while self.running:
            for event in pygame.event.get(pygame.QUIT):
                self.running = 0
            time = self.clock.get_time()
            self.q.update(time)
            self.update(time)
            self.render(time)

            self.clock.tick(60)
        pygame.quit()

    def update(self, time):
        """ Iterate over all processors that update game logic and call their update. """
        [processor.update(time) for processor in self.to_update]

    def render(self, time):
        """ Iterate over all processors that render the game and call their update. """
        [processor.update(time) for processor in self.to_render]
        pygame.display.flip()

    def init_quidditas(self, screen, images):
        """ Initialize the quidditas instance and create the processors. """
        q = quidditas.Quidditas()
        q.add_type_definitions(type_definitions.definitions)

        self.to_update.append(q.add_processor(processors.RenderProcessor(screen, images)))
        self.to_update.append(q.add_processor(processors.AsteroidSpawner()))
        self.to_update.append(q.add_processor(processors.ControlsProcessor(self.event_bus)))
        self.to_render.append(q.add_processor(processors.MovementProcessor((640, 480))))
        return q

if __name__ == "__main__":
    game = Asteroids()
    game.start()
